package com.crr.auth;

import com.auth0.jwt.JWT;
import com.auth0.jwt.algorithms.Algorithm;
import com.auth0.jwt.exceptions.JWTVerificationException;
import com.auth0.jwt.interfaces.Claim;
import com.auth0.jwt.interfaces.DecodedJWT;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;

import java.util.Date;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;

@Component
public class TokenTemplate {
    //秘钥
    @Value("${token.secret}")
    String secret;
    //有效时间 单位s
    @Value("${token.validTime}")
    long validTime;
    private final long DEFAULT_TIME=30*60*1000;//默认30分钟有效期

    /**
     * 生成token
     * @param payload 用户信息
     * @return token字符串
     */
    public String generateToken(Map payload){
        String token= JWT.create()
                .withHeader(getHeader())
                .withPayload(payload)
                .withExpiresAt(getValidate())//给token设置日期限制
                .sign(Algorithm.HMAC256(getSecret()));
        return token;
    }

    Map getHeader(){
        Map map=new HashMap();
        map.put("typ","JWT");
        map.put("alg","HS256");
        return map;
    }
    Date getValidate(){
        Long time=System.currentTimeMillis()+getValidTime();
        Date date=new Date(time);
        return date;
    }
public ValidResult validate(String token){
        if(null==token||"".equals(token))
            return new ValidResult(0,"token为空",null);
            DecodedJWT decodedJWT=null;

            try {
                decodedJWT= JWT.require(Algorithm.HMAC256(secret))
                  .build()
                  .verify(token);
            } catch (JWTVerificationException e) {
                return new ValidResult(0,"token已过期",null);
            } catch (Exception e) {
                return new ValidResult(1,"token失效",null);
            }
Map<String ,Claim> map=decodedJWT.getClaims();
    return new ValidResult(2,"验证成功",convert(map));
}

public String refreshToken(String token){
        ValidResult result=validate(token);
                if(result.getCode()==1){
                return null;
                }else if (result.getCode()==0){
                    //说明过期
                    DecodedJWT decodedJWT=JWT.decode(token);
                    Map<String,Claim> map=decodedJWT.getClaims();
                    //生成新的token
                    return generateToken(convert(map));
                }
                Map map=result.getUser();
                return generateToken(map);
}

Map<String,String> convert(Map<String, Claim> map){
        Map<String,String> m=new HashMap<>();
        map.forEach((k,v)->{
            m.put(k,v.asString());
        });
        return m;
}
    public String getSecret() {
        if(null==secret){
            secret= UUID.randomUUID().toString();//随机生成一个36位字符串
        }
        return secret;
    }

    public void setSecret(String secret) {
        this.secret = secret;
    }

    public long getValidTime() {
        if(validTime==0){
            //赋值默认值
        validTime=DEFAULT_TIME;
        }
        return validTime;
    }

    public void setValidTime(long validTime) {
        this.validTime = validTime;
    }
}
